// $Id: ns.cpp 2 2009-09-02 08:47:42Z joseph2002 $
/*
 * Copyright 2009 Joseph Wu
 * Distributed under the Boost Software License, Version 1.0.
 * (See accompanying file LICENSE_1_0.txt or http://www.boost.org/LICENSE_1_0.txt)
 *
 * For more information, see http://xpcomplus.sourceforge.net
 */

#include <boost/assert.hpp>
#include <boost/algorithm/string.hpp>
#include <xpgen/ns.hpp>

using namespace std;

namespace xpgen {
namespace ns {

void get_ns_list(vector<string>& ns_list, const string& ns)
{
    ns_list.clear();
    if (!ns.empty())
        boost::split(ns_list, ns, boost::is_any_of("."));
}

string get_ns_cpp(const vector<string>& ns_list, size_t n1, size_t n2)
{
    BOOST_ASSERT(0 <= n1 && n1 <= n2 && n2 <= ns_list.size());

    string ret;
    for (size_t i = n1; i < n2; ++i) {
        if (i > n1)
            ret += "::";
        ret += ns_list[i];
    }
    return ret;
}

string get_ns_cpp(const vector<string>& ns_list)
{
    return get_ns_cpp(ns_list, 0, ns_list.size());
}

string get_qname(const string& ns, const string& name)
{
    string ret;
    if (!ns.empty()) {
        ret += ns;
        ret += ".";
    }
    ret += name;
    return ret;
}

string get_qname_cpp(const string& ns_cpp, const string& name)
{
    // XXX Prepend '::' to global name?
    string ret;
    if (!ns_cpp.empty()) {
        ret += ns_cpp;
        ret += "::";
    }
    ret += name;
    return ret;
}

string get_relative_ns_cpp(
        const vector<string>& ns_list, const vector<string>& in_ns_list)
{
    string ret;

    if (ns_list.empty())
        return ret;

    if (in_ns_list.empty()) {
        ret = get_ns_cpp(ns_list, 0, ns_list.size());
        return ret;
    }

    size_t i;
    for (i = 0; i < ns_list.size() && i < in_ns_list.size(); ++i) {
        if (ns_list[i] != in_ns_list[i]) {
            ret = get_ns_cpp(ns_list, 0, ns_list.size());
            return ret;
        }
    }

    if (ns_list.size() == in_ns_list.size()) {
        return ret;
    }

    if (i == ns_list.size()) {
        return ret;
    }

    ret = get_ns_cpp(ns_list, i, ns_list.size());
    return ret;
}

string get_relative_ns_cpp(const string& ns, const string& in_ns)
{
    vector<string> ns_list, in_ns_list;
    get_ns_list(ns_list, ns);
    get_ns_list(in_ns_list, in_ns);
    return get_relative_ns_cpp(ns_list, in_ns_list);
}

} // namespace xpgen::ns
} // namespace xpgen
